﻿namespace PlugNT.Pack.Rss
{
    using System;
    using System.IO;
    using System.Net;
    using System.Text;
    using System.Xml;

    public class Feed
    {
        private DateTime _lastModiFied;
        private DateTime _lastRssDate;
        private string _url;
        private PlugNT.Pack.Rss.Channel channel;

        public Feed()
        {
            this.channel = new PlugNT.Pack.Rss.Channel();
        }

        public Feed(string url, DateTime dt)
        {
            this.channel = new PlugNT.Pack.Rss.Channel();
            this._url = url;
            this._lastRssDate = dt;
        }

        private string Get_CH(string s)
        {
            int l = s.IndexOf("charset=") + 8;
            return s.Substring(l, s.Length - l);
        }

        public void Read()
        {
            XmlDocument xDoc = new XmlDocument();
            HttpWebRequest request = (HttpWebRequest) WebRequest.Create(this._url);
            request.Timeout = 0x4e20;
            request.UserAgent = "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 2.0.40607; .NET CLR 1.1.4322)";
            HttpWebResponse response = (HttpWebResponse) request.GetResponse();
            this._lastModiFied = response.LastModified;
            Stream stream = response.GetResponseStream();
            if (this.Get_CH(response.Headers["Content-Type"].ToString()) == "GBK")
            {
                StreamReader sr = new StreamReader(stream, Encoding.GetEncoding("GB2312"));
                xDoc.Load(sr);
            }
            else
            {
                xDoc.Load(stream);
            }
            if (this._lastRssDate < this._lastModiFied)
            {
                XmlNodeList xnList = xDoc.DocumentElement["channel"].SelectNodes("item");
                int a = xnList.Count;
                foreach (XmlNode xNode in xnList)
                {
                    PlugNT.Pack.Rss.Item rt = new PlugNT.Pack.Rss.Item {
                        Title = xNode.SelectSingleNode("title").InnerText.Replace("'", "''"),
                        Link = xNode.SelectSingleNode("link").InnerText.Replace("'", "''"),
                        Description = xNode.SelectSingleNode("description").InnerText.Replace("'", "''")
                    };
                    try
                    {
                        rt.PubDate = xNode.SelectSingleNode("pubDate").InnerText;
                    }
                    catch
                    {
                        rt.PubDate = this._lastModiFied.ToString();
                    }
                    this.channel.Items.Add(rt);
                }
            }
        }

        public void Write(string filePath)
        {
            StreamWriter rw = new StreamWriter(filePath, false, Encoding.UTF8);
            int tCount = this.channel.Items.Count;
            rw.WriteLine("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>");
            rw.WriteLine("<?xml-stylesheet type=\"text/css\" href=\"rsstyle.css\"?>");
            rw.WriteLine("<rss version=\"2.0\">");
            rw.WriteLine("<channel>");
            rw.WriteLine("<title>" + this.channel.Title + "</title>");
            rw.WriteLine("<link>" + this.channel.Link + "</link>");
            for (int i = 0; i < tCount; i++)
            {
                rw.WriteLine("<item>");
                rw.WriteLine("<title>" + this.channel.Items[i].Title + "</title>");
                rw.WriteLine("<link>" + this.channel.Items[i].Link + "</link>");
                rw.WriteLine("<description><![CDATA[" + this.channel.Items[i].Description + "]]></description>");
                rw.WriteLine("<pubDate>" + this.channel.Items[i].PubDate + "</pubDate>");
                rw.WriteLine("</item>");
            }
            rw.WriteLine("</channel>");
            rw.WriteLine("</rss>");
            rw.Flush();
            rw.Close();
        }

        public void WriteCss(string path)
        {
            string newPath = path.EndsWith("rsstyle.css") ? path : (path + @"\rsstyle.css");
            StreamWriter rw = new StreamWriter(newPath, false, Encoding.UTF8);
            rw.Write(this.Css);
            rw.Flush();
            rw.Close();
        }

        public PlugNT.Pack.Rss.Channel Channel
        {
            get
            {
                return this.channel;
            }
        }

        public string Css
        {
            get
            {
                return "\r\n                channel\r\n                {\r\n\t                font-size: 14pt;\r\n\t                background: white;\r\n\t                margin: 10px;\r\n\t                width: 100%;\r\n\t                font-family: 宋体, 新宋体, verdana, arial, helvetica, sans-serif;\r\n                }\r\n\r\n                managingEditor, webMaster, title, link, description, copyright, lastBuildDate, pubDate \r\n                { \r\n\t                display: block; font-size: medium; \r\n                }\r\n\r\n                rss, item title, item link, item description, item \r\n                {\r\n\t                display: block;\r\n\t                font-weight: normal;\r\n\t                font-size: 12pt;\r\n\t                background-image: none;\r\n\t                margin: 5px;\r\n\t                background-color: #ffffcc;\r\n                }\r\n\r\n                image, image title, image height, image width, image url, category, ttl, generator, guid, language, docs, comments,pubDate\r\n                { \r\n\t                display: none; \r\n                }\r\n\r\n                channel\r\n                {\r\n\t                padding-right: 10px;\r\n\t                padding-left: 10px;\r\n\t                padding-bottom: 10px;\r\n\t                margin: 0px auto;\r\n\t                width: 100%;\r\n\t                padding-top: 10px;\r\n\t                text-align: center;\r\n                }\r\n\r\n                item\r\n                {\r\n\t                padding-right: 10px;\r\n\t                display: block;\r\n\t                padding-left: 10px;\r\n\t                font-size: small;\r\n\t                padding-bottom: 10px;\r\n\t                margin: 20px 0px;\r\n\t                width: 80%;\r\n\t                line-height: 150%;\r\n\t                padding-top: 10px;\r\n\t                border-bottom: red 1px solid;\r\n\t                text-align: left;\r\n                }\r\n\r\n                channel title\r\n                {\r\n\t                display: block;\r\n\t                font-weight: bold;\r\n\t                font-size: large;\r\n\t                z-index: 1;\r\n\t                position: relative;\r\n\t                height: auto;\r\n                }\r\n\r\n                item title { font-weight: bold; font-size: 16px; display: block; height: auto; position: relative; z-index: 1}\r\n                item link { margin-bottom: 9pt; }\r\n                link { display: block; color: blue; text-decoration: underline; }\r\n                info { display: block; margin: 3em 4em 3em 4em; color: Black; background: #FFFACD; border: solid #CCCC66 2px; text-align: center; padding: 1.5em; font-family: mono; font-size: small; }\r\n                ";
            }
        }

        public DateTime LastModiFied
        {
            get
            {
                return this._lastModiFied;
            }
        }

        public DateTime LastRssDate
        {
            set
            {
                this._lastRssDate = value;
            }
        }

        public string url
        {
            get
            {
                return this._url;
            }
            set
            {
                this._url = value;
            }
        }
    }
}

